<?php

declare(strict_types=1);
/**
 * This file is part of habo_new_media.
 *
 * @link     https://www.berlen.cn/
 * @contact  tech@berlen.cn
 * @license  http://gitlab.rehou.cn/habo/habo_new_media/-/blob/master/README.md
 */
namespace app\service\fetch\ocean;

use app\enum\CommonEnum;
use app\enum\ConfigEnum;
use app\enum\OceanEnum;
use app\model\ClientAccountModel;
use app\model\mongo\MongoOeCarouselModel;
use app\service\client\AccountService;
use app\service\fetch\MediaInterface;
use app\service\fetch\MediaService;
use app\service\ocean\MaterialService;
use think\db\exception\DataNotFoundException;
use think\db\exception\DbException;
use think\db\exception\ModelNotFoundException;
use think\Model;

/**
 * 拉取增量图文素材.
 */
final class CarouselService extends MediaService implements MediaInterface
{
    /**
     * @var string 数据拉取key
     */
    protected const FETCH_KEY = ConfigEnum::CACHE_CONFIG[OceanEnum::LIST_CONFIG_LOCK_KEY]['carousel'];

    /**
     * 获取视频素材.
     *
     * @param string $advertiserId 账户id
     * @return bool
     * @throws DataNotFoundException
     * @throws DbException
     * @throws ModelNotFoundException
     */
    public static function getCarouselList(string $advertiserId = ''): bool
    {
        // 获取账户信息
        $obj = AccountService::getAccountModel(0, $advertiserId);
        if (! $obj instanceof ClientAccountModel || ! $obj->getKey()) {
            return self::setError('账户数据不存在');
        }
        // 增量获取上次视频最新时间
        $lastTime = intval(self::getLastVideoTime(intval($obj->getKey())));
        $startDate = '';
        $endDate = '';
        if ($lastTime) {
            $startDate = date('Y-m-d', $lastTime);
            $endDate = date('Y-m-d');
        }
        $page = 0;
        while (true) {
            $result = self::getList($advertiserId, ++$page, $startDate, $endDate);
            if ($result === false) {
                return false;
            }
            if (count($result['data']['carousels']) == 0) {
                break;
            }
            foreach ($result['data']['carousels'] as $item) {
                $model = self::getInfo(intval($obj->getKey()), strval($item['id']));
                if (! $model instanceof MongoOeCarouselModel || ! $model->getKey()) {
                    $model = new MongoOeCarouselModel();
                }
                $item['account_id'] = intval($obj->getKey());
                $item['adv_id'] = $advertiserId;
                $item['carousel_id'] = strval($item['id']);
                $item['carousel_create_time'] = intval(strtotime($item['create_time']));
                $item['carousel_update_time'] = intval(strtotime($item['update_time']));
                $item['version'] = intval(date('Ymd'));
                unset($item['id'],$item['create_time'],$item['update_time']);
                $model->setAttrs($item);
                if (! $model->save()) {
                    return self::setError('保存信息出错');
                }
            }
        }
        return true;
    }

    /**
     * 获取用户最后一个视频的上传时间.
     * @param int $accountId 账户id
     * @return mixed
     */
    private static function getLastVideoTime(int $accountId = 0)
    {
        return (new MongoOeCarouselModel())->where('account_id', $accountId)->max('carousel_create_time');
    }

    /**
     * 拉取图文素材信息.
     *
     * @param string $advertiserId 账户id
     * @param int $page 分页
     * @param string $startDate 开始日期
     * @param string $endDate 结束日期
     * @return bool|mixed|string
     */
    private static function getList(string $advertiserId = '', int $page = 1, string $startDate = '', string $endDate = '')
    {
        $token = AccountService::getToken(CommonEnum::OE_MEDIA, $advertiserId);
        if (! $token) {
            return self::setError('token获取失败');
        }
        $headers = [
            'Access-Token' => $token,
            'Content-Type' => 'application/json',
        ];
        $params = [
            'advertiser_id' => $advertiserId,
            'page' => $page,
            'page_size' => OceanEnum::MAX_CUSTOM_MATERIAL_PAGE_SIZE,
        ];
        if ($startDate && $endDate) {
            $params['filtering'] = [
                'start_time' => $startDate,
                'end_time' => $endDate,
            ];
        }

        return MaterialService::getCarouselList($headers, $params);
    }

    /**
     * 获取图文素材信息.
     *
     * @param int $accountId 账户id
     * @param string $carouselId 图文素材id
     * @return null|array|mixed|Model|MongoOeCarouselModel
     */
    private static function getInfo(int $accountId = 0, string $carouselId = '')
    {
        $where = [
            ['carousel_id', '=', $carouselId],
            ['account_id', '=', $accountId],
        ];

        return (new MongoOeCarouselModel())->where($where)->field(true)->findOrEmpty();
    }
}
